
#pragma once  //pecifies that the file will be included (opened) only once by the compiler when compiling a source code file. 
/*SIGNAL*/
#define SUCESS 1;
#define SYMBOL_EXISTED 2;
#define SYMBOL_NOT_FOUND 3;
#define MAX_SYMBOL_TABLE_OBJECT 32
const int INTEGER_DEFAULT_VALUE = 0;
const int BOOLEAN_DEFAULT_VALUE= 0;

//struct symbolTableObj{
//	char* name; // name of variable or name of function/ procedure
//	int type; // variable or function
//	union{
//		bool bolVlaue;
//		int intValue;
//	}value;
//
//};
class ScopeLevelTable{
private:
	int table[16][2];
public:
	ScopeLevelTable();
	void enterscope(int,int,int); // level, start, end;
	int* leavescope(int);// level return start end
	int* getRange(int); // level return start end
	int* getLocalRange(int);// level return start end
};
class symbolTableObj{

public:
	char* name; // name of variable or name of function/ procedure
	int type; // variable or function
	union{
		bool bolValue;
		int intValue;
	}value;
	//symbolTableObj* next; // the next symbol object in the same scope
	int address;
	symbolTableObj();
};
class SymbolTable{
private:
	const symbolTableObj emptySymbolTableObj;
	symbolTableObj symboltable[MAX_SYMBOL_TABLE_OBJECT];
//	const symbolTableObj* TOP_STACK ;//= &symboltable[MAX_SYMBOL_TABLE_OBJECT];
//	const symbolTableObj* BASE_STACK;// = &symboltable[0];
	int stackSP;
	int currentLevel; 	
	int startItem, endItem;
	symbolTableObj* currentScopeStart; // the first item in the top scope
	symbolTableObj* currentScopeEnd; // the last item in the top scope
	//symbolTableObj* previousScopeStart; // the first item in the top scope
	//symbolTableObj* previousScopeEnd; // the last item in the top scope
	ScopeLevelTable leveltable;
	bool isFirstItemAdded; // flag to show the first item to add into the symbol table
	int currentPosition;
public:
	SymbolTable();
	~SymbolTable();
	//const int  MAX_SYMBOL_TABLE_OBJECT;
	void enterScope();
	void leaveScope();
	symbolTableObj* lookup_symbol_entry(char name[]);
	int insert_symbol_entry(symbolTableObj& symbol);
	symbolTableObj* remove_symbol_entry();
	bool isEmpty() const;
	int size() const;
	const int getObjectPosition(symbolTableObj&) const; // return the address of the last visit symbol object in the stack
	symbolTableObj* top();
	symbolTableObj* getSymbolObj(int);	
};
